// Based on D:\Program Files\Boost\boost_1_48_0\boost\mpl\negate.hpp


#ifndef des_table_adjuster_HPP__
#define des_table_adjuster_HPP__

#include <climits> //CHAT_BIT

#include <boost/mpl/integral_c.hpp>
#include <boost/mpl/aux_/msvc_eti_base.hpp>
#include <boost/mpl/aux_/na_spec.hpp>
#include <boost/mpl/aux_/lambda_support.hpp>
#include <boost/mpl/aux_/config/eti.hpp>
#include <boost/mpl/aux_/config/integral.hpp>
#include <boost/mpl/aux_/config/static_constant.hpp>

#include <boost/mpl/at.hpp>

namespace boost { namespace mpl {

	//typedef boost::mpl::vector_c<int, 6, 4, 2, 0, -2, -4, -6, -8> temp_table;	//TODO: renombrar
	//typedef boost::mpl::vector_c<int, -1, -1, -1, -1, -1, -1, -1, -1> temp_table;	//TODO: renombrar
	//typedef boost::mpl::vector_c<int, 13, 9,  5,  1, -3, -7, -11, -15> temp_table;	//TODO: renombrar

	template< typename Tag > 
	struct des_table_adjuster_impl;

	template< typename T > 
	struct des_table_adjuster_tag
	{
		typedef typename T::tag type;
	};

	template< typename Table, typename BOOST_MPL_AUX_NA_PARAM(N) >
	struct des_table_adjuster
#if !defined(BOOST_MPL_CFG_MSVC_ETI_BUG)
		: des_table_adjuster_impl< 
		typename des_table_adjuster_tag<N>::type
		>::template apply<Table, N>::type
#else
		: aux::msvc_eti_base< typename apply_wrap1<
		des_table_adjuster_impl< typename des_table_adjuster_tag<N>::type >
		, N
		>::type >::type
#endif
	{
		BOOST_MPL_AUX_LAMBDA_SUPPORT(1, des_table_adjuster, (N))
	};

	BOOST_MPL_AUX_NA_SPEC(1, des_table_adjuster)


#if defined(BOOST_MPL_CFG_NO_NESTED_VALUE_ARITHMETIC)
		namespace aux {
			template< typename T, T n > 
			struct des_table_adjuster_wknd
			{
				BOOST_STATIC_CONSTANT(T, value = n + boost::mpl::at_c< temp_table, ( (n-1) % CHAR_BIT ) >::type::value);
				typedef integral_c<T,value> type;
			};
	}
#endif

	template<>
	struct des_table_adjuster_impl<integral_c_tag>
	{
#if defined(BOOST_MPL_CFG_NO_NESTED_VALUE_ARITHMETIC)
		template< typename Table, typename N > 
		struct apply
			: aux::des_table_adjuster_wknd< typename N::value_type, N::value >
#else
		template< typename Table, typename N > 
		struct apply
			: integral_c< typename N::value_type, (N::value + boost::mpl::at_c< Table, ( (N::value-1) % CHAR_BIT ) >::type::value) >

			//: integral_c< typename N::value_type, (N::value + boost::mpl::at_c< temp_table, ( (N::value-1) % CHAR_BIT ) >::type::value) >

#endif    
		{
		};
	};

}}	//namespace boost::mpl

#endif // des_table_adjuster_HPP__
